package com.opencee.common.security;

import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.annotation.JSONField;
import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;

/**
 * 自定义认证信息
 *
 * @author liuyadu
 */
public class SecurityUser implements UserDetails {
    private static final long serialVersionUID = -123308657146774881L;
    /**
     * 用户ID
     */
    private Long userId;

    /**
     * 登录名
     */
    private String username;
    /**
     * 密码
     */
    @JsonIgnore
    @JSONField(serialize = false)
    private String password;

    /**
     * 用户权限
     */
    private Collection<GrantedAuthority> authorities = Collections.emptyList();
    /**
     * 认证客户端ID
     */
    private String clientId;

    /**
     * 用户状态
     */
    private Integer status;

    /**
     * 账号启用
     */
    private boolean accountEnabled = true;

    /**
     * 账号未过期
     */
    private boolean accountNonExpired = true;
    /**
     * 账号未锁定
     */
    private boolean accountNonLocked = true;
    /**
     * 密钥为过期
     */
    private boolean credentialsNonExpired = true;

    /**
     * 用户资料
     */
    private JSONObject profile = new JSONObject();

    /**
     * 只是客户端模式.不包含用户信息
     *
     * @return
     */
    @JsonProperty("isClientOnly")
    public Boolean isClientOnly() {
        return clientId != null && userId == null;
    }


    @Override
    public Collection<? extends GrantedAuthority> getAuthorities() {
        if (authorities == null) {
            return Collections.EMPTY_LIST;
        }
        return this.authorities;
    }

    @Override
    public String getPassword() {
        return this.password;
    }

    @Override
    public String getUsername() {
        return this.username;
    }

    @Override
    public boolean isAccountNonExpired() {
        return accountNonExpired;
    }

    @Override
    public boolean isAccountNonLocked() {
        return accountNonLocked;
    }

    @Override
    public boolean isCredentialsNonExpired() {
        return credentialsNonExpired;
    }

    @Override
    public boolean isEnabled() {
        return accountEnabled;
    }

    public Long getUserId() {
        return userId;
    }

    public void setUserId(Long userId) {
        this.userId = userId;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public String getClientId() {
        return clientId;
    }

    public void setClientId(String clientId) {
        this.clientId = clientId;
    }

    @JsonDeserialize(using = GrantedDateAuthorityDeserializer.class)
    public void setAuthorities(Collection<? extends GrantedAuthority> authorities) {
        this.authorities = new ArrayList<GrantedAuthority>(authorities);
    }


    public JSONObject getProfile() {
        return profile;
    }

    public void setProfile(JSONObject profile) {
        this.profile = profile;
    }


    public Integer getStatus() {
        return status;
    }

    public void setStatus(Integer status) {
        this.status = status;
    }

    public boolean isAccountEnabled() {
        return accountEnabled;
    }

    public void setAccountEnabled(boolean accountEnabled) {
        this.accountEnabled = accountEnabled;
    }

    public void setAccountNonExpired(boolean accountNonExpired) {
        this.accountNonExpired = accountNonExpired;
    }

    public void setAccountNonLocked(boolean accountNonLocked) {
        this.accountNonLocked = accountNonLocked;
    }

    public void setCredentialsNonExpired(boolean credentialsNonExpired) {
        this.credentialsNonExpired = credentialsNonExpired;
    }

    /**
     * 添加用户属性
     *
     * @param key
     * @param value
     */
    public void put(String key, Object value) {
        if (this.profile == null) {
            this.profile = new JSONObject();
        }
        this.profile.put(key, value);
    }
}
